package com.trendytech.tds.common.filter;

import java.util.ArrayList;
import java.util.Collection;
import java.util.List;
import java.util.Locale;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.http.HttpMethod;
import org.springframework.security.core.Authentication;
import org.springframework.security.core.GrantedAuthority;
import org.springframework.security.core.context.SecurityContextHolder;
import org.springframework.security.web.authentication.WebAuthenticationDetails;
import org.springframework.web.servlet.HandlerInterceptor;
import org.springframework.web.servlet.LocaleResolver;
import org.springframework.web.servlet.ModelAndView;
import org.springframework.web.servlet.support.RequestContextUtils;

import com.trendytech.tds.common.util.LocaleHolder;
import com.trendytech.tds.entity.OperationLog;
import com.trendytech.tds.entity.User;

public class AuthenticationInerceptor implements HandlerInterceptor {
	protected Log logger = LogFactory.getLog(getClass());

	public static final long SESSION_EXPIRE_TIME = 30;
	
/*	@Autowired
	private IUserService userService;
	@Autowired
	private IResourceService resService;
	@Autowired
	private IOperationLogService operationLogService;*/
	
	private String dashboardUrl;
	public void setDashboardUrl(String dashboardUrl) {
		this.dashboardUrl = dashboardUrl;
	}
	
	@Override
	public void afterCompletion(HttpServletRequest request,
			HttpServletResponse response, Object arg2, Exception arg3)
			throws Exception {

	}

	@Override
	public void postHandle(HttpServletRequest request,
			HttpServletResponse response, Object arg2, ModelAndView arg3)
			throws Exception {

	}

	@Override
	public boolean preHandle(HttpServletRequest request,
			HttpServletResponse response, Object handler) throws Exception {

		// 处理国际化
		LocaleResolver localeResolver = RequestContextUtils
				.getLocaleResolver(request);
		Locale locale = localeResolver.resolveLocale(request);
		LocaleHolder.setLocale(locale);
		// 设置人员信息、权限等属性
		setAttributes(request);
		// 记录操作日志
		recordOperation(request);

		return true;
	}

	/**
	 * Set common attributes including UserInfo and basePath
	 * @param request
	 * @param response
	 */
	private void setAttributes(HttpServletRequest request) {
		
		/*// Get authentication info from spring security
		Authentication auth = SecurityContextHolder.getContext()
				.getAuthentication();
		// Current user info including auth info
		UserInfo userInfo = new UserInfo();
		if(auth != null){
			// Login username
			String username = auth.getName();
			// User info from db
			User user = userService.getByUsername(username);
			// Auth detail from spring security
			WebAuthenticationDetails details = (WebAuthenticationDetails)
					auth.getDetails();
			
			BeanUtils.copyProperties(user, userInfo);
			BeanUtils.copyProperties(details, userInfo);
			List<String> list = new ArrayList<String>();
			// Set granted auth to UserInfo
			for (GrantedAuthority ga : auth.getAuthorities()) {
				list.add(ga.getAuthority());
			}
			userInfo.setAuthorities(list);
		}
		
		request.setAttribute("basePath", request.getContextPath());
		request.setAttribute("user", userInfo);
		
		Collection<String> info = user.getAuthorities();
		for (String infos : info) {
			if(infos.contains("ROLE_ADMIN")){
				request.setAttribute("infos", infos);
			}
		}
		request.setAttribute("dashboardUrl", dashboardUrl);
		UserInfo user = (UserInfo)request.getAttribute("user");
		Collection<String> info = user.getAuthorities();
		if(info!=null){
			for (String infos : info) {
				if("ROLE_ADMIN".equals(infos)){
					request.setAttribute("infos", infos);
				}
			}
		}
		
		this.setSupportType(request);*/
	}
	
	/**
	 * 设置支持的存储方式
	 * @param request
	 */
	private void setSupportType(HttpServletRequest request) {
/*		request.setAttribute("SUPPORT_FS", Constants.SUPPORT_FS);
		request.setAttribute("SUPPORT_BLOCK", Constants.SUPPORT_BLOCK);
		request.setAttribute("SUPPORT_OBJECT", Constants.SUPPORT_OBJECT);*/
	}
	
	/**
	 * 记录操作日志
	 * @param request
	 */
	private void recordOperation(HttpServletRequest request) {
		if (isAjaxRequest(request) && 
				!request.getMethod().equalsIgnoreCase(HttpMethod.GET.name())) {
			// 当前请求地址
			String requri = request.getServletPath();
			// 当前请求资源信息
			//Resource currentRes = resService.getByUrl(requri);
/*			if (currentRes != null) {
				UserInfo user = (UserInfo) request.getAttribute("user");
				String userId = user.getId();
				OperationLog operationLog = new OperationLog(
						userId, currentRes.getId());
				operationLog.setIp(getIp(request));
				//TODO 操作日志 写死
				operationLog.setResult(1);
				//operationLogService.insert(operationLog);
*/			/*}*/
		}
	}

	public static boolean isAjaxRequest(HttpServletRequest request) {
		return ("XMLHttpRequest".equalsIgnoreCase(request
				.getHeader("X-Requested-With")));
	}

	/**
	 * 获取客户端ip地址
	 * @param request
	 * @return
	 */
	private static String getIp(HttpServletRequest request) {
		String ip = request.getHeader("x-forwarded-for");
		if (ip == null || ip.length() == 0 || "unknown".equalsIgnoreCase(ip)) {
			ip = request.getHeader("Proxy-Client-IP");
		}
		if (ip == null || ip.length() == 0 || "unknown".equalsIgnoreCase(ip)) {
			ip = request.getHeader("WL-Proxy-Client-IP");
		}
		if (ip == null || ip.length() == 0 || "unknown".equalsIgnoreCase(ip)) {
			ip = request.getRemoteAddr();
		}
		if (ip == null || ip.length() == 0 || "unknown".equalsIgnoreCase(ip)) {
			ip = request.getHeader("http_client_ip");
		}
		if (ip == null || ip.length() == 0 || "unknown".equalsIgnoreCase(ip)) {
			ip = request.getHeader("HTTP_X_FORWARDED_FOR");
		}
		// 如果是多级代理，那么取第一个ip为客户ip
		if (ip != null && ip.indexOf(",") != -1) {
			ip = ip.substring(ip.lastIndexOf(",") + 1, ip.length()).trim();
		}
		return ip;
	}
}
